feat(subtitle): add ZapCap captions provider#128
Conversation
Add ZapCap as a subtitle/captions provider so OpenMontage can burn animated, word-synced caption templates (Hormozi, Beast, Devin, ...) into a video via the ZapCap API. - tools/subtitle/zapcap_captions.py: new `zapcap_captions` BaseTool (capability=subtitle, provider=zapcap, runtime=API). Wraps the full flow — upload (local file or URL) -> create task -> poll -> download — with a granular `action` dispatcher (list_templates, upload, create_task, get_task, approve_transcript, balance) for multi-template / multi-language fan-out via transcript_task_id + translate_to. Auth via ZAPCAP_API_KEY; pinned to https://api.zapcap.ai. - .agents/skills/zapcap-captions/SKILL.md: Layer 3 skill (flow, templates, renderOptions schema, translation/fan-out, failure modes). - docs: PROVIDERS.md provider section + env summary, AGENT_GUIDE.md Layer 3 table row, README.md subtitles row, .env.example key. Subtitle capability is now 3 providers (subtitle_gen, remotion_caption_burn, zapcap_captions). Verified end-to-end against api.zapcap.ai: free FFmpeg render -> ZapCap caption -> downloaded MP4, transcript accurate. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
rajpratham1
left a comment
There was a problem hiding this comment.
This is a substantial but well-structured feature addition that integrates ZapCap as a new subtitle provider across the project. The implementation is comprehensive—it includes the provider implementation, documentation, configuration, agent skills, and environment setup, making it straightforward for users to adopt. The separation between the provider logic and the existing subtitle tools is also clearly documented, and the granular API actions (upload, create_task, get_task, etc.) provide good flexibility for more advanced workflows.
calesthio
left a comment
There was a problem hiding this comment.
Thank you for the contribution. ZapCap is a real value-add for OpenMontage: styled, animated, word-synced social captions are materially different from plain SRT generation or local subtitle burn-in, and the tool has the right high-level shape: provider metadata, fallback tools, Layer 3 skill linkage, setup docs, and unavailable status when ZAPCAP_API_KEY is missing.
I need to request changes before merge because this adds a new 559-line paid/network provider without focused offline contract tests. Per docs/PR_REVIEW_GUIDE.md, provider additions should have at least contract/metadata, registry discovery, and status behavior coverage, with mocked API tests preferred over live-provider tests. This PR currently has no tests/ coverage for zapcap_captions.
Verification I ran:
python -m py_compile tools/subtitle/zapcap_captions.py
# passed
python -c "from tools.subtitle.zapcap_captions import ZapCapCaptions; from tools.tool_registry import registry; registry.discover(); print([t.name for t in registry.get_by_capability('subtitle')]); print(ZapCapCaptions().get_status())"
# ['subtitle_gen', 'zapcap_captions', 'remotion_caption_burn']
# ToolStatus.UNAVAILABLE
Please add focused mocked tests covering at minimum:
- registry discovery under
capability='subtitle' get_status()with no key, missingrequests, and configured key- local missing-file failure for
input_path - template-name resolution / not-found behavior
- mocked happy path for upload -> create_task -> poll -> download, including artifact/output data
- one mocked API error path that verifies useful error reporting without leaking secrets
I did not find an actionable security issue in the reviewed diff, but the lack of provider tests is too much merge risk for this class of tool.
Address PR review: add focused mocked tests for the new paid/network provider. All network I/O is stubbed at the tool's _request/_download boundary — no live api.zapcap.ai calls, no API key required. Covers: - registry discovery under capability="subtitle" + contract metadata - get_status(): no key / missing requests / configured key - local missing-file failure for input_path (and asserts no network call) - template-name resolution (case-insensitive) + not-found lists options - mocked happy path: upload -> create_task -> poll -> download, asserting videoId/taskId/templateId/output/artifacts and the full request lifecycle (>=2 polls) - mocked API error path: actionable error, API key never leaked - task status=failed surfaces the upstream error 13 tests, all passing (python -m pytest tests/tools/test_zapcap_captions.py). Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
|
Thanks for the review — added focused offline contract tests in Mapping to the requested coverage:
Extra: |
What
Adds ZapCap as a subtitle/captions provider so OpenMontage can burn animated, word-synced caption templates (Hormozi, Beast, Devin, ...) into a video via the ZapCap API.
Changes
tools/subtitle/zapcap_captions.py— newzapcap_captionsBaseTool(capability=subtitle,provider=zapcap,runtime=API). Wraps the full flow — upload (local file or URL) → create task → poll → download — with a granularactiondispatcher (list_templates,upload,create_task,get_task,approve_transcript,balance) for multi-template / multi-language fan-out viatranscript_task_id+translate_to..agents/skills/zapcap-captions/SKILL.md— Layer 3 skill: flow, templates,renderOptionsschema, translation/fan-out, failure modes.docs/PROVIDERS.mdprovider section + env summary,AGENT_GUIDE.mdLayer 3 table row,README.mdsubtitles row,.env.examplekey.Subtitle capability goes from 2 → 3 providers (
subtitle_gen,remotion_caption_burn,zapcap_captions).Configuration
Single env var:
ZAPCAP_API_KEY(requires a ZapCap Pro plan + API credits).Verification
Verified end-to-end against
api.zapcap.ai: free FFmpeg render → ZapCap caption (Hormozi 1 / Beast templates) → downloaded MP4.list_templatesreturns 29 templates; transcript came back accurate; output is a valid 1080×1920 MP4 with captions burned in.Notes
.envandprojects/(verification artifacts) are gitignored and not included.🤖 Generated with Claude Code